﻿using System.Linq;
using System.Text;
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Net;
using Microsoft.Xna.Framework.Storage;

namespace TheGame
{
    //Gestisce grafica ed effetti sonori del personaggio principale
    public class Abe : Character
    {
        #region VARS
        public SoundEffect Sound_PASS;
        public SoundEffect Sound_TURN;
        public SoundEffect Sound_JUMP;
        public SoundEffect Sound_RUNSTOP;
        public SoundEffect Sound_SNEAK;
        public SoundEffect Sound_IMPACT;
        public SoundEffect Sound_HELLO;
        public SoundEffect Sound_FOLLOW;
        public SoundEffect Sound_WAIT;
        public SoundEffect Sound_ROLL;
        public SoundEffect Sound_OK;
        public SoundEffect Sound_OMM;
        public SoundEffect Sound_COMMANDJUMP;
        public SoundEffect Sound_COMMANDRUNJUMP;

        public Animation BOMBDEACTIVATE;
        public Animation BOMBDEACTIVATEFAIL;

        public Animation BOMBEXPLODE;


        public Animation PASS_1;
        public Animation PASS_2;
        public Animation PASS_3;

        public Animation STOP;

        public Animation STOP_1;
        public Animation STOP_2;
        public Animation STOP_3;

        public Animation WAIT;
        public Animation WAITcROUCH;

        public Animation ROLL1;
        public Animation ROLL2;
        public Animation ROLL3;

        public Animation TURN;
        public Animation TURNdOWN;

        public Animation JUMPUP;

        public Animation JUMPDOWN;

        public Animation HUNG;
        public Animation HUNGLONG;

        public Animation BLOCK;

        public Animation BLOCK_1;
        public Animation BLOCK_2;

        public Animation HOISTUP;
        public Animation HOISTDOWN;

        public Animation HOISTuP_1;
        public Animation HOISTuP_2;

        public Animation HOISTdOWN_1;
        public Animation HOISTdOWN_2;


        public Animation GODOWN;
        public Animation PLANE;

        public Animation JUMP_1;
        public Animation JUMP_2;
        public Animation JUMP_3;
        public Animation JUMP_4;

        public Animation CROUCH;
        public Animation STANDUP;

        public Animation RUN_1;
        public Animation RUN_2;
        public Animation RUN_3;
        public Animation RUN_4;
        public Animation RUN_5;
        public Animation RUNsTOP_1;
        public Animation RUNsTOP_2;
        public Animation RUNJUMP1;
        public Animation RUNJUMP2;
        public Animation RUNJUMP3;
        public Animation RUNJUMP4;

        public Animation SNEAK_1;
        public Animation SNEAK_2;
        public Animation SNEAK_3;
        public Animation SNEAKsTOP;

        public Animation HELLO;
        public Animation FOLLOW;
        public Animation WAITME;
        public Animation COMMANDJUMP;
        public Animation COMMANDRUNJUMP;

        public Animation KO;
        public Animation GETUP;

        public Animation DIE;
        public Animation OMM;
        public Animation NOTCONTROL;

        public Animation PULLEVER;

        public Animation ENTERDOOR;
        public Animation EXITDOOR;

        Texture2D aBE_BBOX_PNG;
        Texture2D aBE_NOISE;
        public bool AbeNoise = false;
        public Rectangle NOISE;
        public Rectangle NoNOISE;
        public bool ABEisSTEALTH = false; 


        public List<Character> MUDOKONS = new List<Character>();

        public List<Slig> SLIGS = new List<Slig>();
        

        public string SAYS = "";
        public AbeControl Control;
        #endregion

        public Abe(Game1 game)
        {
            this.game = game;
            MUDOKONS.Add(this);

            POSITION = 0;

            ///////////////////////////////////////////////////////////////////

            Sound_PASS = game.Content.Load<SoundEffect>("Sound\\PASS");
            Sound_TURN = game.Content.Load<SoundEffect>("Sound\\TURN");
            Sound_JUMP = game.Content.Load<SoundEffect>("Sound\\JUMP");
            Sound_RUNSTOP = game.Content.Load<SoundEffect>("Sound\\RUNSTOP");
            Sound_SNEAK = game.Content.Load<SoundEffect>("Sound\\SNEAK");
            Sound_IMPACT = game.Content.Load<SoundEffect>("Sound\\IMPACT");
            Sound_HELLO = game.Content.Load<SoundEffect>("Sound\\HELLO");
            Sound_FOLLOW = game.Content.Load<SoundEffect>("Sound\\FOLLOW");
            Sound_WAIT = game.Content.Load<SoundEffect>("Sound\\WAIT");
            Sound_ROLL = game.Content.Load<SoundEffect>("Sound\\ROLL");
            Sound_OK = game.Content.Load<SoundEffect>("Sound\\OK");
            Sound_COMMANDJUMP = game.MudokonFactory.Sound_COMMANDJUMP;
            Sound_COMMANDRUNJUMP = game.MudokonFactory.Sound_COMMANDRUNJUMP;
            Sound_OMM = game.Content.Load<SoundEffect>("Sound\\OMM");

            ////////////////////////////////////////////////////////////////

            BOMBDEACTIVATE = new Animation(game.MudokonFactory.BombDeactivate_R, game.MudokonFactory.BombDeactivate_L, AnimateRate, 26, "BOMBDEACTIVATE", 0, 0, -1, 10, 10);
            BOMBDEACTIVATEFAIL = new Animation(game.MudokonFactory.BombDeactivateFail_R, game.MudokonFactory.BombDeactivateFail_L, AnimateRate, 21, "BOMBDEACTIVATEFAIL", 0, 0, -1, 10, 10);

            BOMBEXPLODE = new Animation(game.MudokonFactory.BombExplode_C, game.MudokonFactory.BombExplode_C, AnimateRate, 13, "BOMBEXPLODE", 0, 0, -1, 10, 10);

            WAITcROUCH = new Animation(game.MudokonFactory.WaitCrouch_R, game.MudokonFactory.WaitCrouch_L, 1000 / 6, 6, "WAITcROUCH", 0, 0, -1, 10, 10);

            WAIT = new Animation(game.MudokonFactory.Wait_R, game.MudokonFactory.Wait_L, 1000 / 6, 6, "WAIT", 0, 0, -1, 15, 15);
            TURN = new Animation(game.MudokonFactory.Turn_L, game.MudokonFactory.Turn_R, AnimateRate, 12, "TURN", new Sound(Sound_TURN, 2, 0.05f), 0, 0, -1, 10, 10);

            STOP = new Animation(game.MudokonFactory.Stop_R, game.MudokonFactory.Stop_L, AnimateRate, 4, "STOP", new Sound(Sound_PASS, 4), 0, 0, -1, 43, 43);
            PASS_1 = new Animation(game.MudokonFactory.Walk_1PASS_R, game.MudokonFactory.Walk_1PASS_L, AnimateRate, 7, "PASS_1", new Sound(Sound_PASS, 4), 1, 0, 6, 0, 43);
            PASS_2 = new Animation(game.MudokonFactory.Walk_2PASS_R, game.MudokonFactory.Walk_2PASS_L, AnimateRate, 9, "PASS_2", new Sound(Sound_PASS, 6), 1, 0, 8, 43, 86);
            PASS_3 = new Animation(game.MudokonFactory.Walk_3PASS_R, game.MudokonFactory.Walk_3PASS_L, AnimateRate, 9, "PASS_3", new Sound(Sound_PASS, 6), 1, 0, 8, 86, 129);

            BLOCK = new Animation(game.MudokonFactory.Block_R, game.MudokonFactory.Block_L, AnimateRate, 21, "BLOCK", new Sound(Sound_RUNSTOP, 9), 0, 0, -1, 20, 20);

            SNEAKsTOP = new Animation(game.MudokonFactory.SneakStop_R, game.MudokonFactory.SneakStop_L, AnimateRate, 4, "SNEAKsTOP", 0, 0, -1, 53, 53);
            SNEAK_1 = new Animation(game.MudokonFactory.Sneak1_R, game.MudokonFactory.Sneak1_L, AnimateRate, 6, "SNEAK_1", new Sound(Sound_SNEAK, 3), 1, 0, 5, 10, 53);
            SNEAK_2 = new Animation(game.MudokonFactory.Sneak2_R, game.MudokonFactory.Sneak2_L, AnimateRate, 10, "SNEAK_2", new Sound(Sound_SNEAK, 7), 1, 0, 9, 53, 96);
            SNEAK_3 = new Animation(game.MudokonFactory.Sneak3_R, game.MudokonFactory.Sneak3_L, AnimateRate, 10, "SNEAK_3", new Sound(Sound_SNEAK, 7), 1, 0, 9, 96, 139);

            RUN_1 = new Animation(game.MudokonFactory.Run1_R, game.MudokonFactory.Run1_L, AnimateRate, 4, "RUN_1", 2, 0, 3, 35, 35);
            RUN_2 = new Animation(game.MudokonFactory.Run2_R, game.MudokonFactory.Run2_L, AnimateRate, 2, "RUN_2", new Sound(Sound_PASS, 2), 2, 0, 4, 35, 78);
            RUN_3 = new Animation(game.MudokonFactory.Run3_R, game.MudokonFactory.Run3_L, AnimateRate, 3, "RUN_3", 2, 0, 9, 78, 121);
            RUN_4 = new Animation(game.MudokonFactory.Run4_R, game.MudokonFactory.Run4_L, AnimateRate, 5, "RUN_4", new Sound(Sound_PASS, 5), 2, 0, 9, 121, 164);
            RUN_5 = new Animation(game.MudokonFactory.Run5_R, game.MudokonFactory.Run5_L, AnimateRate, 6, "RUN_5", 2, 0, 9, 164, 207);
            RUNsTOP_1 = new Animation(game.MudokonFactory.RunStop1_R, game.MudokonFactory.RunStop1_L, AnimateRate, 8, "RUNSTOP_1", new Sound(Sound_RUNSTOP, 3), 1, 0, 7, 121, 164);
            RUNsTOP_2 = new Animation(game.MudokonFactory.RunStop2_R, game.MudokonFactory.RunStop2_L, AnimateRate, 8, "RUNsTOP_S", 1, 0, 7, 164, 207);
            RUNJUMP1 = new Animation(game.MudokonFactory.RunJump1_R, game.MudokonFactory.RunJump1_L, AnimateRate, 2, "RUNJUMP1", 1, 0, 1, 0, 43,0,0);
            RUNJUMP2 = new Animation(game.MudokonFactory.RunJump2_R, game.MudokonFactory.RunJump2_L, AnimateRate, 5, "RUNJUMP2", 1, 0, 7, 43, 86,0,50);
            RUNJUMP3 = new Animation(game.MudokonFactory.RunJump3_R, game.MudokonFactory.RunJump3_L, AnimateRate, 4, "RUNJUMP3", 1, 0, 7, 86, 129,50,50);
            RUNJUMP4 = new Animation(game.MudokonFactory.RunJump4_R, game.MudokonFactory.RunJump4_L, AnimateRate, 5, "RUNJUMP4", 1, 0, 7, 129, 172,50,0);

            JUMP_1 = new Animation(game.MudokonFactory.Jump1_R, game.MudokonFactory.Jump1_L, AnimateRate, 10, "JUMP_1", 1, 0, 3, 18, 61);
            JUMP_2 = new Animation(game.MudokonFactory.Jump2_R, game.MudokonFactory.Jump2_L, AnimateRate, 3, "JUMP_2", 1, 0, 3, 61, 104);
            JUMP_3 = new Animation(game.MudokonFactory.Jump3_R, game.MudokonFactory.Jump3_L, AnimateRate, 3, "JUMP_3", 1, 0, 3, 104, 147);
            JUMP_4 = new Animation(game.MudokonFactory.Jump4_R, game.MudokonFactory.Jump4_L, AnimateRate, 6, "JUMP_4", new Sound(Sound_JUMP, 1), 0, 0, -1, 147, 147);

            ROLL1 = new Animation(game.MudokonFactory.Roll1_R, game.MudokonFactory.Roll1_L, AnimateRate, 5, "ROLL1", new Sound(Sound_ROLL, 2), 0, 0, -1, 10, 53);
            ROLL2 = new Animation(game.MudokonFactory.Roll2_R, game.MudokonFactory.Roll2_L, AnimateRate, 3, "ROLL2", new Sound(Sound_ROLL, 2), 0, 0, -1, 53, 96);
            ROLL3 = new Animation(game.MudokonFactory.Roll3_R, game.MudokonFactory.Roll3_L, AnimateRate, 3, "ROLL3", new Sound(Sound_ROLL, 2), 0, 0, -1, 96, 139);
            WAITcROUCH = new Animation(game.MudokonFactory.WaitCrouch_R, game.MudokonFactory.WaitCrouch_L, 1000 / 6, 6, "WAITcROUCH", 0, 0, -1, 10, 10);
            TURNdOWN = new Animation(game.MudokonFactory.TurnDown_L, game.MudokonFactory.TurnDown_R, AnimateRate, 8, "TURNdOWN", new Sound(Sound_TURN, 2, 0.05f), 0, 0, -1, 10, 10);
            CROUCH = new Animation(game.MudokonFactory.Crouch_R, game.MudokonFactory.Crouch_L, AnimateRate, 9, "CROUCH", 0, 0, -1, 10, 10);
            STANDUP = new Animation(game.MudokonFactory.StandUp_R, game.MudokonFactory.StandUp_L, AnimateRate, 9, "STANDUP", 0, 0, -1, 10, 10);

            JUMPDOWN = new Animation(game.MudokonFactory.JumpDown_R, game.MudokonFactory.JumpDown_L, AnimateRate, 18, "JUMOdOWN", new Sound(Sound_JUMP, 7), 0, -1, 10, 15, 15, 50, 0);
            JUMPUP = new Animation(game.MudokonFactory.JumpUp_R, game.MudokonFactory.JumpUp_L, AnimateRate, 14, "JUMPuP", new Sound(Sound_PASS, 13, true, game, this), 0, 1, 13, 15, 15, 0, 50);
            HUNG = new Animation(game.MudokonFactory.Hung_R, game.MudokonFactory.Hung_L, 1000 / 6, 6, "HUNG", 0, 0, -1, 15, 15, 60, 60);
            HUNGLONG = new Animation(game.MudokonFactory.HungLong_R, game.MudokonFactory.HungLong_L, AnimateRate, 15, "HUNGLONG", 0, 0, -1, 20, 20, 60, 60);

            HOISTUP = new Animation(game.MudokonFactory.HoistUp_R, game.MudokonFactory.HoistUp_L, AnimateRate, 23, "HOISTUP", 0, 0, -1, 15, 15, 0, 150);
            HOISTDOWN = new Animation(game.MudokonFactory.HoistDown_R, game.MudokonFactory.HoistDown_L, AnimateRate, 23, "HOISTDOWN", 0, 0, -1, 15, 15, 150, 0);

            //DOWNPLANE = new Animation(game.MudokonFactory.DownPlane_R, game.MudokonFactory.DownPlane_L, AnimateRate, 21, "DOWNPLANE", new Sound(Sound_IMPACT, 14), 0, 0, -1, 47, 90, 200, 0);
            GODOWN = new Animation(game.MudokonFactory.GoDown_R, game.MudokonFactory.GoDown_L, AnimateRate, 9, "GODOWN", 1, -2, 5, 12, 55, 200, 50);
            PLANE = new Animation(game.MudokonFactory.Plane_R, game.MudokonFactory.Plane_L, AnimateRate, 12, "PLANE", new Sound(Sound_IMPACT, 3), 1, 0, 2, 55, 98, 50, 0);

            HELLO = new Animation(game.MudokonFactory.Wait_R, game.MudokonFactory.Wait_L, 1000 / 6, 6, "HELLO", new Sound(Sound_HELLO, 1), 0, 0, -1, 15, 15);
            FOLLOW = new Animation(game.MudokonFactory.Wait_R, game.MudokonFactory.Wait_L, 1000 / 6, 6, "FOLLOW", new Sound(Sound_FOLLOW, 1), 0, 0, -1, 15, 15);
            WAITME = new Animation(game.MudokonFactory.Wait_R, game.MudokonFactory.Wait_L, 1000 / 6, 6, "WAITME", new Sound(Sound_WAIT, 1), 0, 0, -1, 15, 15);
            COMMANDJUMP = new Animation(game.MudokonFactory.Wait_R, game.MudokonFactory.Wait_L, 1000 / 6, 6, "COMMANDJUMP", new Sound(Sound_COMMANDJUMP, 1), 0, 0, -1, 15, 15);
            COMMANDRUNJUMP = new Animation(game.MudokonFactory.Wait_R, game.MudokonFactory.Wait_L, 1000 / 6, 6, "COMMANDRUNJUMP", new Sound(Sound_COMMANDRUNJUMP, 1), 0, 0, -1, 15, 15);


            KO = new Animation(game.MudokonFactory.Ko_R, game.MudokonFactory.Ko_L, AnimateRate, 13, "KO", new Sound(Sound_IMPACT, 3), 0, 0, -1, 46, 46);
            GETUP = new Animation(game.MudokonFactory.GetUp_R, game.MudokonFactory.GetUp_L, AnimateRate, 13, "GETUP", 0, 0, -1, 46, 46);

            DIE = new Animation(game.MudokonFactory.Die_R, game.MudokonFactory.Die_L, AnimateRate, 28, "DIE", 0, 0, -1, 50, 50);

            PULLEVER = new Animation(game.MudokonFactory.PulLever_R, game.MudokonFactory.PulLever_L, AnimateRate, 19, "PULLEVER", 0, 0, -1, 6, 6);

            OMM = new Animation(game.MudokonFactory.Omm_R, game.MudokonFactory.Omm_L, AnimateRate, 16, "OMM", new Sound(Sound_OMM, 1), 0, 0, -1, 10, 10);
            NOTCONTROL = new Animation(game.MudokonFactory.Omm_R, game.MudokonFactory.Omm_L, AnimateRate, 16, "NOTCONTROL", 0, 0, -1, 10, 10);

            ENTERDOOR = new Animation(game.MudokonFactory.EnterDoor_R, game.MudokonFactory.EnterDoor_L, 1000 / 15, 12, "ENTERDOOR", 0, 0, -1, 15, 15);
            EXITDOOR = new Animation(game.MudokonFactory.ExitDoor_R, game.MudokonFactory.ExitDoor_L, 1000 / 15, 11, "EXITDOOR", 0, 0, -1, 15, 15);


            CurrentLevel = game.CurrentLevel;
            NoNOISE = new Rectangle(-50, -50, 0, 0);
            NOISE = NoNOISE;
            CurrentAnimation = WAIT;
            canmove = true;
            Direction = 1;
            color = Color.White;
            aBE_BBOX_PNG = game.Content.Load<Texture2D>("Sprite_Sheet\\Abe\\ABE_BBOX");
            aBE_NOISE = game.Content.Load<Texture2D>("Sprite_Sheet\\Abe\\NoiseAbe");
            DrawingRec = new Rectangle(-18 + 43 * 4, 400 - CurrentAnimation.SpriteHeight, CurrentAnimation.SpriteWidth, CurrentAnimation.SpriteHeight);
            boundingBox = new Rectangle(6 + 43*4, 285, 44, 150);//42
        }

        //Gestisce la spritesheet dell'animazione corrente.
        //Definisce quale frame della spritesheet deve essere disegnato.
        public void AnimateAbe(Animation anim)
        {          
            if (anim.CurrentFrame == 0)
            {
                PrevAnimation = CurrentAnimation;
                PrevAnimation.Reset();
                CurrentAnimation = anim;
                
                if (Direction == 1)
                {
                    DrawingRec.X = DrawingRec.X + (PrevAnimation.xEND - CurrentAnimation.xSTART);
                }
                else
                {
                    DrawingRec.X = DrawingRec.X + ((PrevAnimation.SpriteLWidth - PrevAnimation.xEND) - (CurrentAnimation.SpriteLWidth - CurrentAnimation.xSTART));
                }
                              
                DrawingRec.Y = DrawingRec.Y - (PrevAnimation.yEND - CurrentAnimation.ySTART) + (PrevAnimation.SpriteHeight - CurrentAnimation.SpriteHeight);

                if (CurrentAnimation == TURN || CurrentAnimation == TURNdOWN)
                {
                    Direction = Direction * -1;
                }
               
                if (Direction == 1)
                {
                    anim.SpriteWidth = anim.SpriteRWidth;
                    anim.SpriteHeight = anim.SpriteRHeight;
                    anim.Sheet = anim.SheetR;
                }
                else
                {
                    anim.SpriteWidth = anim.SpriteLWidth;
                    anim.SpriteHeight = anim.SpriteLHeight;
                    anim.Sheet = anim.SheetL;
                }

                DrawingRec.Width = anim.SpriteWidth;
                DrawingRec.Height = anim.SpriteHeight;

                this.game.spriteCurrent = anim.Sheet;
            }
         
            if (anim.Time > anim.AnimateRate)
            {
                if (anim.CurrentFrame == 1)
                {
                    boundingBox.X += (anim.xEND - anim.xSTART) * Direction;
                    boundingBox.Y = DrawingRec.Bottom - (anim.yEND + boundingBox.Height);
                }
                anim.Time = 0f;
                if (anim.Effect != null && anim.CurrentFrame == anim.Effect.FrameToPlay)
                    anim.Effect.Play();

                if (anim.CurrentFrame == anim.FrameCount)
                {
                    anim.LastFrameDone = true;                   
                }
                else
                    anim.LastFrameDone = false;

                if (anim.CurrentFrame < anim.FrameCount)
                {
                    anim.SourceRect = new Rectangle(anim.CurrentFrame * anim.SpriteWidth, 0, anim.SpriteWidth, anim.SpriteHeight);
                    this.game.sourceRect = anim.SourceRect;
                    anim.Forward();
                }
            }
        }
        #region Attribute
        public Rectangle BoundigBox
        {
            get { return boundingBox; }
            set { boundingBox = value; }
        }

        public Texture2D ABE_BBOX_PNG
        {
            get { return aBE_BBOX_PNG; }
        }
        public Texture2D ABE_NOISE
        {
            get { return aBE_NOISE; }
        }

        public bool CanMove
        {
            get { return canmove; }
            set { canmove = value; }
        }

        public int PassesDone
        {
            get
            {
                return passesDone;
            }
            set
            {
                passesDone = value;
            }
        } 
        #endregion      
    }   
}
